﻿/*
 * tcpclientdevice.cpp
 *
 *  Created on: 2016年12月20日
 *      Author: work
 */
#include <dm/export.hpp>

#define DM_API_OS_COM DM_API_EXPORT

#include <dm/os/com/tcpclientdevice.hpp>
#include <dm/os/log/logger.hpp>

namespace dm{
namespace os{
namespace com{

static const char* logModule = "CTcpClientDevice.com.os.dm";

CTcpClientDevice::CTcpClientDevice( ios_t& ios,size_t rxBufSize ):
		CDevice(rxBufSize),m_dev(ios){
	log().debug(THISMODULE "创建对象");
}

CTcpClientDevice::~CTcpClientDevice(){
	log().debug(THISMODULE "销毁对象");
	m_dev.shutdown(m_dev.shutdown_both);
	m_dev.close();
}

bool CTcpClientDevice::checkAndSetAddress( const CTcpClientAddr& addr ){
	m_addr = addr;
	return true;
}

bool CTcpClientDevice::startConnect(){
	const CTcpClientAddr* addr = m_addr.asTcpClient();
	if( !addr ){
		log().warnning(THISMODULE "没有可用地址信息");
		return false;
	}

	try{
		if( m_dev.is_open() ){
			boost::system::error_code e;
			m_dev.shutdown(m_dev.shutdown_both,e);
			m_dev.close(e);
//			return false;
		}

		// open操作
		m_dev.async_connect(end_t(ip_t::from_string(addr->getServerHost().c_str()),addr->getServerPort()),
				boost::bind(&CTcpClientDevice::handler_connect,this,boost::asio::placeholders::error));
	}catch( std::exception& ec ){
		return false;
	}

	return true;
}

bool CTcpClientDevice::stopConnect(){
	try{
		m_dev.shutdown( m_dev.shutdown_both );
		m_dev.close();
		error_t ec;
		handler_disconnect(ec);
	}catch( std::exception& e ){
		log().warnning(THISMODULE "关闭设备异常%s",e.what());
		return false;
	}

	return true;
}

bool CTcpClientDevice::startSend( const dm::uint8* buf,const size_t& len ){
	try{
		boost::asio::async_write( m_dev,
				boost::asio::buffer(buf,len),
				boost::bind(&CTcpClientDevice::handler_tx,this,
						boost::asio::placeholders::error)
		);
	}catch( std::exception& e ){
		log().warnning(THISMODULE "send %d bytes fail(%s)",len,e.what());
		return false;
	}

	return true;
}

void CTcpClientDevice::start_rx(){
	try{
		m_dev.async_receive(boost::asio::buffer(m_rxBuf.get(),m_rxBufSize),
				boost::bind(&CTcpClientDevice::handler_rx,this,
						boost::asio::placeholders::error,
						boost::asio::placeholders::bytes_transferred )
				);
	}catch( std::exception& ec ){
		log().error(THISMODULE "开启监听失败%s",ec.what());
	}
}

void CTcpClientDevice::cancelDev(){
	try{
		m_dev.cancel();
	}catch( std::exception& ec ){
		log().error(THISMODULE "取消设备失败%s",ec.what());
	}
}

}
}
}


